home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1996 May: Tool Chest / Developer CD Series May 1996 (Tool Chest) (Apple Computer) (1996).iso / Tool Chest / Development Tools & Languages / Dylan Related / Mindy / Mindy 1.2 - portable sources / libraries / dylan / cond.dylan < prev    next >
Encoding:
Text File  |  1995-03-15  |  7.4 KB  |  314 lines  |  [TEXT/ttxt]

  1. module: Dylan
  2. author: William Lott (wlott@cs.cmu.edu)
  3. rcs-header: $Header: cond.dylan,v 1.9 94/10/26 20:18:54 wlott Exp $
  4.  
  5. //======================================================================
  6. //
  7. // Copyright (c) 1994  Carnegie Mellon University
  8. // All rights reserved.
  9. // 
  10. // Use and copying of this software and preparation of derivative
  11. // works based on this software are permitted, including commercial
  12. // use, provided that the following conditions are observed:
  13. // 
  14. // 1. This copyright notice must be retained in full on any copies
  15. //    and on appropriate parts of any derivative works.
  16. // 2. Documentation (paper or online) accompanying any system that
  17. //    incorporates this software, or any part of it, must acknowledge
  18. //    the contribution of the Gwydion Project at Carnegie Mellon
  19. //    University.
  20. // 
  21. // This software is made available "as is".  Neither the authors nor
  22. // Carnegie Mellon University make any warranty about the software,
  23. // its performance, or its conformity to any specification.
  24. // 
  25. // Bug reports, questions, comments, and suggestions should be sent by
  26. // E-mail to the Internet address "gwydion-bugs@cs.cmu.edu".
  27. //
  28. //======================================================================
  29. //
  30. // This file implements the condition system.
  31. //
  32.  
  33.  
  34. // Classes
  35.  
  36. define class <condition> (<object>)
  37. end class <condition>;
  38.  
  39.  
  40. define class <serious-condition> (<condition>)
  41. end class <serious-condition>;
  42.  
  43.  
  44. define class <error> (<serious-condition>)
  45. end class <error>;
  46.  
  47.  
  48. define class <simple-condition> (<condition>)
  49.   slot condition-format-string,
  50.     required-init-keyword: format-string:;
  51.   slot condition-format-arguments,
  52.     init-keyword: format-arguments:,
  53.     init-value: #();
  54. end class <simple-condition>;
  55.  
  56.  
  57. define class <simple-error> (<error>, <simple-condition>)
  58. end class <simple-error>;
  59.  
  60.  
  61. define class <type-error> (<error>)
  62.   slot type-error-value, init-keyword: value:;
  63.   slot type-error-expected-type, init-keyword: type:;
  64. end class <type-error>;
  65.  
  66.  
  67. define class <warning> (<condition>)
  68. end class <warning>;
  69.  
  70.  
  71. define class <simple-warning> (<warning>, <simple-condition>)
  72. end class <simple-warning>;
  73.  
  74.  
  75. define class <restart> (<condition>)
  76. end class <restart>;
  77.  
  78.  
  79. define class <simple-restart> (<restart>, <simple-condition>)
  80. end class <simple-restart>;
  81.  
  82.  
  83. define class <abort> (<restart>)
  84.   slot abort-description :: <byte-string>,
  85.     init-keyword: description:,
  86.     init-value: "<abort>";
  87. end class <abort>;
  88.  
  89.  
  90. // Condition reporting.
  91.  
  92. define generic report-condition (condition, stream);
  93.  
  94. define variable *format-function* =
  95.   method (stream, string, #rest arguments)
  96.     apply(format, string, arguments);
  97.   end;
  98.  
  99. define variable *force-output-function* =
  100.   method (stream)
  101.     fflush();
  102.   end;
  103.  
  104. define method report-condition (condition :: <condition>, stream)
  105.   *format-function*(stream, "%=", condition);
  106. end method report-condition;
  107.  
  108.  
  109. define method report-condition (condition :: <simple-condition>, stream)
  110.   apply(*format-function*, stream,
  111.     condition.condition-format-string,
  112.     condition.condition-format-arguments);
  113. end method report-condition;
  114.  
  115.  
  116. define method report-condition (condition :: <type-error>, stream)
  117.   *format-function*(stream,
  118.             "%= is not of type %=",
  119.             condition.type-error-value,
  120.             condition.type-error-expected-type);
  121. end method report-condition;
  122.  
  123.  
  124. define method report-condition (condition :: <abort>, stream)
  125.   *format-function*(stream, "%s", condition.abort-description);
  126. end method report-condition;
  127.  
  128.  
  129. // Condition signaling
  130.  
  131. define method signal (string :: <string>, #rest arguments)
  132.   signal(make(<simple-warning>,
  133.           format-string: string,
  134.           format-arguments: arguments));
  135. end method signal;
  136.  
  137.  
  138. define method signal (cond :: <condition>, #rest noise)
  139.   unless (empty?(noise))
  140.     error("Can only supply format arguments when supplying a format string.");
  141.   end;
  142.   local
  143.     method search (h)
  144.       if (h)
  145.     if (instance?(cond, h.handler-type))
  146.       let test = h.handler-test;
  147.       if (~test | test(cond))
  148.         let remaining = h.handler-next;
  149.         h.handler-function(cond, method () search(remaining) end);
  150.       else
  151.         search(h.handler-next);
  152.       end if;
  153.     else
  154.       search(h.handler-next);
  155.     end if;
  156.       else
  157.     default-handler(cond);
  158.       end if;
  159.     end method search;
  160.   search(current-handler());
  161. end method signal;
  162.  
  163.  
  164. define method error (string :: <string>, #rest arguments)
  165.   error(make(<simple-error>,
  166.          format-string: string,
  167.          format-arguments: arguments));
  168. end method error;
  169.  
  170.  
  171. define method error (cond :: <condition>, #rest noise)
  172.   unless (empty?(noise))
  173.     error("Can only supply format arguments when supplying a format string.");
  174.   end;
  175.   signal(cond);
  176.   invoke-debugger(make(<simple-error>,
  177.                format-string:
  178.              "Attempt to return from a call to error"));
  179. end method error;
  180.  
  181.  
  182. define method cerror (restart-descr, cond-or-string, #rest arguments)
  183.   block ()
  184.     apply(error, cond-or-string, arguments);
  185.   exception (<simple-restart>,
  186.          init-arguments: list(format-string: restart-descr,
  187.                   format-arguments: arguments))
  188.     #f;
  189.   end block;
  190. end method cerror;
  191.  
  192.  
  193. define method type-error (value, type)
  194.   error(make(<type-error>, value: value, type: type));
  195. end method type-error;
  196.  
  197.  
  198. define method check-type (value, type)
  199.   if (instance?(value, type))
  200.     value;
  201.   else
  202.     type-error(value, type);
  203.   end if;
  204. end method check-type;
  205.  
  206. define method abort ()
  207.   error(make(<abort>));
  208. end method abort;
  209.  
  210.  
  211. define method default-handler (condition :: <condition>)
  212.   #f;
  213. end method default-handler;
  214.  
  215.  
  216. define method default-handler (condition :: <serious-condition>)
  217.   invoke-debugger(condition);
  218. end method default-handler;
  219.  
  220.  
  221. define method default-handler (condition :: <warning>)
  222.   report-condition(condition);
  223.   #f;
  224. end method default-handler;
  225.  
  226.  
  227. define method default-handler (restart :: <restart>)
  228.   error("No restart handler for %=", restart);
  229. end method default-handler;
  230.  
  231.  
  232.  
  233. // Breakpoints.
  234.  
  235. define class <breakpoint> (<simple-warning>)
  236. end class <breakpoint>;
  237.  
  238.  
  239. define method return-allowed? (cond :: <breakpoint>)
  240.   #t;
  241. end method return-allowed?;
  242.  
  243.  
  244. define method return-query (cond :: <breakpoint>)
  245.   #f;
  246. end method return-query;
  247.  
  248.  
  249. define method return-description (cond :: <breakpoint>)
  250.   "Return #f";
  251. end method return-description;
  252.  
  253.  
  254. define method %break (string :: <string>, #rest arguments)
  255.   %break(make(<breakpoint>,
  256.           format-string: string,
  257.           format-arguments: arguments));
  258. end method %break;
  259.  
  260.  
  261. define method %break (cond :: <condition>, #rest noise)
  262.   unless (empty?(noise))
  263.     error("Can only supply format arguments when supplying a format string.");
  264.   end unless;
  265.   block ()
  266.     invoke-debugger(cond);
  267.   exception (<simple-restart>,
  268.          init-arguments: list(format-string: "Continue from break"))
  269.     #f;
  270.   end block;
  271. end method %break;
  272.  
  273.  
  274. define method break (#rest arguments)
  275.   if (empty?(arguments))
  276.     %break("Break.");
  277.   else
  278.     apply(%break, arguments);
  279.   end if;
  280. end method break;
  281.  
  282.  
  283.  
  284. // Introspection.
  285.  
  286. define method do-handlers (function :: <function>)
  287.   for (h = current-handler() then h.handler-next,
  288.        while h)
  289.     function(h.handler-type,
  290.          h.handler-test | method (x) #t end,
  291.          h.handler-function,
  292.          h.handler-init-args);
  293.   end for;
  294. end method do-handlers;
  295.  
  296.  
  297. define method return-allowed? (cond :: <condition>)
  298.   #f;
  299. end method return-allowed?;
  300.  
  301.  
  302. define generic return-description (cond);
  303.  
  304.  
  305. // Interactive handling.
  306.  
  307. define method restart-query (restart :: <restart>)
  308.   #f;
  309. end method restart-query;
  310.  
  311.  
  312. define generic return-query (condition);
  313.  
  314.